#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>

#include "msq.h"
#include "priority_msq.h"

static void get_mq_by_priority(int priority, MsgQueue *q);

MsgQueue *q1;
MsgQueue *q2;
MsgQueue *q3;

void pmsq_init(MsgQueue *q) {
    printf("Initializing pmsq_init...\n");
    q1 = (MsgQueue *)malloc(sizeof(MsgQueue));
    q2 = (MsgQueue *)malloc(sizeof(MsgQueue));
    q3 = (MsgQueue *)malloc(sizeof(MsgQueue));

    init_queue(q1);
    init_queue(q2);
    init_queue(q3);
}

// 入队（阻塞）
void pmsq_enqueue(int priority, int value) {
    printf("pmsq_enqueue, try to get lock...\n");
    MsgQueue q;
    get_mq_by_priority(priority, &q);
    enqueue(&q, value);
    printf("pmsq_enqueue end!\n");
}

static void get_mq_by_priority(int priority, MsgQueue *q) {
    if (priority == LOW) {
        q = q1;
    } else if (priority == MEDIUM) {
        q = q2;
    } else if (priority == HIGH) {
        q = q3;
    } else {
        printf("Invalid priority level\n");
        return NULL;
    }
}
// 出队（阻塞）
int dequeue(MsgQueue *q) {
    printf("dequeue, try to get the lock...\n"); 
    pthread_mutex_lock(&q->mutex);
    printf("Greate! Get lock\n");
    while (q->count == 0) {
        printf("queue is empty, so wait...\n");
        // 队列空，等待 not_empty 条件变量
        pthread_cond_wait(&q->not_empty, &q->mutex);
    }
    int value = q->buffer[q->head];
    q->head = (q->head + 1) % QUEUE_SIZE;
    q->count--;
    pthread_cond_signal(&q->not_full); // 唤醒生产者
    pthread_mutex_unlock(&q->mutex);
    printf("dequeue end\n");

    return value;
}